package com.itibo.common;

import com.itibo.comparator.ComparatorByAuthor;
import com.itibo.comparator.ComparatorByGenre;
import com.itibo.comparator.ComparatorByName;
import com.itibo.comparator.ComparatorByYear;
import com.itibo.models.CSVDocument;
import com.itibo.models.Document;
import com.itibo.models.Song;
import com.itibo.models.SongCollection;
import com.itibo.services.SongProcessor;
import com.itibo.services.SongReader;
import com.itibo.services.SongWriter;

import javax.annotation.PostConstruct;
import javax.faces.bean.ManagedBean;
import javax.faces.bean.RequestScoped;
import javax.faces.bean.SessionScoped;
import javax.faces.model.SelectItem;
import java.util.*;

@ManagedBean(name = "songsBean")
@SessionScoped
public class SongsBean {

    private List<SelectItem> availableSortModes;
    private String sortMode;

    public Song getFilterSong() {
        return filterSong;
    }

    public void setFilterSong(Song filterSong) {
        this.filterSong = filterSong;
    }

    private Song filterSong;
    private String message;
    private SongCollection songsCollection;

    public SongProcessor getSongsProcessor() {
        return songsProcessor;
    }

    public void setSongsProcessor(SongProcessor songsProcessor) {
        this.songsProcessor = songsProcessor;
    }

    private SongProcessor songsProcessor;
    private Map<String,Comparator<Song>> allComparators;
    public SongsBean() {
        message = "";
        songsCollection = new SongCollection();
    }

    @PostConstruct
    public void init() {
        initSongProcessor();
        filterSong=new Song();
        availableSortModes = new ArrayList<SelectItem>();
        availableSortModes.add(new SelectItem("name", "Sort By Name"));
        availableSortModes.add(new SelectItem("author", "Sort By Author"));
        availableSortModes.add(new SelectItem("genre", "Sort By Genre"));
        availableSortModes.add(new SelectItem("year", "Sort By Year"));
        allComparators=new HashMap<String,Comparator<Song>>();
        allComparators.put("name",new ComparatorByName());
        allComparators.put("author",new ComparatorByAuthor());
        allComparators.put("year",new ComparatorByYear());
        allComparators.put("genre",new ComparatorByGenre());
    }

    public void processDocument(Document doc) {
        message = "Document in Process";
        SongReader songReader = new SongReader(doc);
        songsCollection = songReader.getSongsCollection();
        initSongProcessor();
    }

    public String getMessage() {
        return message;
    }

    public void setMessage(String message) {
        this.message = message;
    }

    public SongCollection getSongsCollection() {
        return songsCollection;
    }

    public void setSongsCollection(SongCollection songsCollection) {
        this.songsCollection = songsCollection;
    }

    public List<SelectItem> getAvailableSortModes() {
        return availableSortModes;
    }

    public void setAvailableSortModes(List<SelectItem> availableSortModes) {
        this.availableSortModes = availableSortModes;
    }

    public String getSortMode() {
        return sortMode;
    }

    public void setSortMode(String sortMode) {
        this.sortMode = sortMode;
    }

    public void doSort() {
        songsProcessor.sort(allComparators.get(sortMode));
    }
    public void doSearch(){
        songsProcessor.filter(filterSong);
    }

    public void initSongProcessor() {
        songsProcessor = new SongProcessor(songsCollection.clone());
    }

    public List<Song> getSongs() {
        return songsProcessor.getCollectionOfSongs().getMySongs();
    }
    public  void clearFilter(){
        filterSong=new Song();
    }
    public Document exportDocument(){
        Document doc = new CSVDocument();
        SongWriter songWriter = new SongWriter(doc);
        songWriter.putSongCollection(songsProcessor.getCollectionOfSongs());
        return doc;
    }

    public void download() {
        message = "download";
    }
}
